﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using NHibernate;
using NHibernate.Criterion;
using Work.BL.Managers;
using Work.BL.POCOs;
using Work.DAL.Hibernate.Abstract;
using Work.DAL.Hibernate.Entities;
using Work.Tools.ObjectMapper;

namespace Work.BL.Hibernate.Managers
{
    public class HResumeManager : IResumeManager
    {
        #region Fields

        private readonly ICWSessionFactory _sessionFactory;
        private readonly IObjectMapper _objectMapper;

        #endregion

        #region Constructors

        public HResumeManager(ICWSessionFactory sessionFactory, IObjectMapper objectMapper)
        {
            this._sessionFactory = sessionFactory;
            this._objectMapper = objectMapper;
        }

        #endregion

        #region IEducationManager Members

        public ResumePOCO Insert(ResumePOCO resumePoco)
        {
            using (ISession session = this._sessionFactory.CreateSession())
            {
                Resume resume = _objectMapper.Map<ResumePOCO, Resume>(resumePoco);
                session.Save(resume);
                session.Flush();
                return _objectMapper.Map<Resume, ResumePOCO>(resume);
            }
        }

        public ResumePOCO Block(ResumePOCO resumePoco)
        {
            using (ISession session = this._sessionFactory.CreateSession())
            {
                Resume resume = _objectMapper.Map<ResumePOCO, Resume>(resumePoco);
                if (resume.IsBlocked)
                {
                    resume.IsBlocked = false;
                }
                else
                {
                    resume.IsBlocked = true;
                }
                session.Save(resume);
                session.Flush();
                return _objectMapper.Map<Resume, ResumePOCO>(resume);
            }
        }

        public int GetResumeCount()
        {
            using (ISession session = this._sessionFactory.CreateSession())
            {
                int rowCount = session.CreateCriteria<Resume>()
                    .SetProjection(Projections.RowCount()).UniqueResult<int>();
                return rowCount;
            }
        }

        public void Delete(ResumePOCO resumePoco)
        {
            using (ISession session = this._sessionFactory.CreateSession())
            {
                Resume resume = _objectMapper.Map<ResumePOCO, Resume>(resumePoco);
                session.Delete(resume);
                session.Flush();
            }
        }

        public List<ResumePOCO> GetResume()
        {
            using (ISession session = this._sessionFactory.CreateSession())
            {
                IList<Resume> resumes = session.CreateCriteria<Resume>().List<Resume>();
                return resumes
                    .Select(r => this._objectMapper.Map<Resume, ResumePOCO>(r))
                    .ToList();
            }
        }

        public List<ResumePOCO> GetResume(int startIndex, int maxCount)
        {
            using (ISession session = this._sessionFactory.CreateSession())
            {
                IList<Resume> regions = session.CreateCriteria<Resume>()
                    .SetFirstResult(startIndex)
                    .SetMaxResults(maxCount)
                    .List<Resume>();
                return regions
                    .Select(r => this._objectMapper.Map<Resume, ResumePOCO>(r))
                    .ToList();
            }
        }

        public ResumePOCO GetResumeById(int id)
        {
            using (ISession session = this._sessionFactory.CreateSession())
            {
                Resume resume = session.Get<Resume>(id);
                return _objectMapper.Map<Resume, ResumePOCO>(resume);
            }
        }

        public ResumePOCO Edit(ResumePOCO resumePoco)
        {
            using (ISession session = this._sessionFactory.CreateSession())
            {
                Resume resume = _objectMapper.Map<ResumePOCO, Resume>(resumePoco);
                session.Update(resume);
                session.Flush();
                return _objectMapper.Map<Resume, ResumePOCO>(resume);
            }
        }

        #endregion

    }
}
